package xyz.xiangyushui.subtitleConverter;

import java.io.BufferedReader;
import java.io.BufferedWriter;
import java.io.File;
import java.io.FileInputStream;
import java.io.FileNotFoundException;
import java.io.FileOutputStream;
import java.io.IOException;
import java.io.InputStreamReader;
import java.io.OutputStreamWriter;
import java.util.function.Consumer;
import java.util.regex.Matcher;
import java.util.regex.Pattern;
import xyz.xiangyushui.subtitleConverter.exception.InvalidTimePointException;
import xyz.xiangyushui.subtitleConverter.exception.SrtErrorException;

public class SrtTimeLineUpdater {
	private File file;
	private String fileEncode;
	
	public SrtTimeLineUpdater(String filePath){
		this.file=new File(filePath);
		this.fileEncode="utf-8";
	}
	
	/**
	 * early the subtitle timeline
	 * @param second
	 */
	public void early(int second){
		update(second, t->t.decrease(second));
	}
	
	/**
	 * delay subtitle timeLine
	 * @param second
	 */
	public void delay(int second){
		update(second, t->t.increase(second));
	}
	
	private void update(int second,Consumer<TimePoint> f){
		BufferedReader br = null;
		StringBuffer bf=new StringBuffer();
		try {
			br = new BufferedReader(new InputStreamReader(new FileInputStream(
					file),fileEncode));
			String line ;
			while ((line = br.readLine())!= null) {
				String[] timePoints=getTimePoint(line);
				if (timePoints[0]!="") {
					for (String timePoint : timePoints) {
						TimePoint tp=new TimePoint(timePoint);
						f.accept(tp);
						line = line.replace(timePoint, tp.toString());
					}
				}
				System.out.println(line);
				bf.append(line);
				bf.append(System.getProperty("line.separator"));
			}
			write(bf.toString());
		} catch (FileNotFoundException e) {
			System.out.println("srt file not found!");
			e.printStackTrace();
		} catch (IOException e) {
			e.printStackTrace();
		} catch (SrtErrorException e) {
			System.out.println(e.getMessage());
			e.printStackTrace();
		} catch (InvalidTimePointException e) {
			System.out.println(e.getMessage());
			e.printStackTrace();
		} finally {
			if (br != null) {
				try {
					br.close();
				} catch (IOException e) {
					br = null;
				}
			}
		}
	}
	
	private String[] getTimePoint(String line) throws SrtErrorException{
		String[] tps={"",""};
		Matcher m = Pattern.compile("(\\d{1,}):(\\d{2}):(\\d{2})([.,])(\\d{1,})").matcher(line);
		int i=0;
		while(m.find()){
			if(i>1){
				throw new SrtErrorException("invalid srt file at "+line);
			}
			tps[i]=m.group();
			i++;
		}
		return tps;
	}
	
	private void write(String content) {
		BufferedWriter bw = null;
		try {
			bw = new BufferedWriter(new OutputStreamWriter(
				    new FileOutputStream(file),fileEncode));
			bw.write(content);
		} catch (Exception e) {
			e.printStackTrace();
		} finally {
			if (bw != null) {
				try {
					bw.close();
				} catch (IOException e) {
					bw = null;
				}
			}
		}
	}
	
	private static void usage(){
		System.err.println("usage:java SubtitleEditor early/delay seconds pathSrcFile");
		System.exit(-1);
	}


	public static void main(String[] args) {
		System.out.println("This tool only supports srt file with utf8 encoding");
		if(args.length!=3){
			usage();
		}
		int second=0;
		try{
			second=Integer.parseInt(args[1]);
		}catch(NumberFormatException e){
			usage();
		}
		SrtTimeLineUpdater se=new SrtTimeLineUpdater(args[2]);
		switch (args[0]){
			case "early":se.early(second);break;
			case "delay":se.delay(second);break;
			default:usage();
		}		
	}
	
	
}
